package com.signway.harmony_demo.point;

import com.signway.harmony_demo.utils.CommonData;
import com.signway.harmony_demo.utils.LogUtil;
import ohos.agp.components.Component;
import ohos.agp.render.Canvas;
import ohos.agp.render.Paint;
import ohos.agp.utils.Color;
import ohos.agp.utils.Point;
import ohos.app.Context;
import ohos.multimodalinput.event.TouchEvent;

import java.util.ArrayList;
import java.util.List;

public class DrawPoint extends Component implements Component.DrawTask {
    private static final int STROKE_WIDTH = 15;
    private static final String TAG = CommonData.TAG + DrawPoint.class.getSimpleName();
    private final boolean isLocal;
    private float[] pointXs;
    private float[] pointYs;
    private boolean[] isLastPoints;
    private Paint paint;
    private OnDrawCallBack callBack;
    private List<MyPoint> localPoints = new ArrayList<>();
    private List<MyPoint> remotePoints = new ArrayList<>();


    public DrawPoint(Context context, boolean isLocal) {
        super(context);
        this.isLocal = isLocal;
        init();
    }

    private void init() {
        paint = new Paint();
        paint.setAntiAlias(true);
        paint.setStyle(Paint.Style.STROKE_STYLE);
        paint.setStrokeWidth(STROKE_WIDTH);
        addDrawTask(this);

        setTouchEventListener((component, touchEvent) -> {
            int crtX = (int) touchEvent.getPointerPosition(touchEvent.getIndex()).getX();
            int crtY = (int) touchEvent.getPointerPosition(touchEvent.getIndex()).getY();
            MyPoint point = new MyPoint(crtX, crtY);

            switch (touchEvent.getAction()) {
                case TouchEvent.PRIMARY_POINT_UP: {
                    point.setLastPoint(true);
                    localPoints.add(point);
                    callBack.callBack(localPoints);
                    LogUtil.info(TAG, "up:" + crtY);
                } break;
                case TouchEvent.PRIMARY_POINT_DOWN: {
                    localPoints.add(point);
                    LogUtil.info(TAG, "down:" + crtY);
                } break;
                case TouchEvent.POINT_MOVE: {
                    localPoints.add(point);
//                    LogUtil.info(TAG, "move:" + crtY);
                } break;
            }

            invalidate();
            return true;
        });
    }

    public void setDrawParams(boolean[] isLastPoints, float[] pointXs, float[] pointYs) {
        this.pointXs = pointXs;
        this.pointYs = pointYs;
        this.isLastPoints = isLastPoints;
        invalidate();
    }

    public void setOnDrawBack(OnDrawCallBack drawCallBack) {
        callBack = drawCallBack;
    }

    @Override
    public void onDraw(Component component, Canvas canvas) {
        remotePoints.clear();
        if (pointXs != null && pointXs.length > 1) {
            for (int i = 0; i < pointXs.length; i++) {
                float finalX = pointXs[i];
                float finalY = pointYs[i];
                boolean isLast = isLastPoints[i];
                remotePoints.add(new MyPoint(finalX, finalY, isLast));
            }

            drawPoints(canvas, remotePoints, false);
        }
        drawPoints(canvas, remotePoints, true);
    }

    private void drawPoints(Canvas canvas, List<MyPoint> points, boolean isStudent) {
        if (points.size() < 1) {
            return;
        }
        if (isStudent) {
            paint.setColor(isLocal ? Color.BLACK : Color.RED);
        } else {
            paint.setColor(isLocal ? Color.RED: Color.BLACK);
        }
        Point first = null;
        Point last = null;
        for (MyPoint myPoint : points) {
            float finalX = myPoint.getPositionX();
            float finalY = myPoint.getPositionY();
            Point finalPoint = new Point(finalX, finalY);
            if (myPoint.isLastPoint()) {
                first = null;
                last = null;
                continue;
            }
            if (first == null) {
                first = finalPoint;
            } else {
                if (last != null) {
                    first = last;
                }
                last = finalPoint;
                canvas.drawLine(first, last, paint);
            }
        }
    }

    public interface OnDrawCallBack {
        void callBack(List<MyPoint> points);
    }
}
